<?php
/* 
 * The Environment class is responsible for the
 * PHP environment like upload limits and other variables.
 */
class Environment {
    /**
     * The function checks whether files can be uploaded or not according
     * to the settings in the PHP ini.
     * @return <boolean> true if files can be uploaded and false if not.
     */
    function canUpload() {
        if(strtolower(@ini_get('file_uploads')) == 'off' || @ini_get('file_uploads') == 0)
            return(false);
        return(true);
    }

    /**
     * This function gets the PHP ini entries for upload_max_filesize and post_max_size.
     * Converts them to bytes and returns the smaller number.
     * @return <number> returns the smaller of upload_max_filesize and post_max_size.
     */
    function determineMaxUpload()
    {
        $maxFileSize=0;
        $fileSize = ini_get('upload_max_filesize');
        $maxFileSize = $this->convertFromIniValue($fileSize,$unit);

        $postSize = ini_get('post_max_size');
        $postSize = $this->convertFromIniValue($postSize,$unit);
        if($postSize < $maxFileSize)
            return($postSize);
        return($maxFileSize);
    }

    /**
     * TODO: tests needed.
     * This function takes an entry from the php ini e.g.: 123 mb and converts
     * it to bytes so that values become comparable.
     * @param <string> contains the entry from the PHP ini
     * @return <number> returns number of bytes
     */
    function convertFromIniValue($value,&$unit) {
        $value = strtolower($value);
        $value = str_replace("tb","T",$value);
        $value = str_replace("t","T",$value);
        $value = str_replace("gb","G",$value);
        $value = str_replace("g","G",$value);
        $value = str_replace("mb","M",$value);
        $value = str_replace("m","M",$value);
        $value = str_replace("kb","K",$value);
        $value = str_replace("k","K",$value);
        $value = str_replace("bytes","B",$value);
        $value = str_replace("b","B",$value);
        $val = substr($value,0,strlen($value)-1);
        $unit = substr($value,strlen($value)-1);
        switch($unit) {
            case 'T' :  $val *= 1024;	$unit="G";
            case 'G' :  $val *= 1024;	$unit="M";
            case 'M' :  $val *= 1024;	$unit="K";
            case 'K' :  $val *= 1024;	$unit="B";
                        break;
            default  :  $val = $value; 	$unit="B";
        }
        return($val);
    }
    /**
     * This function takes a value and its unit (T,G,M,K,B) and then
     * determines the largest possible unit that can be used to represent the value.
     * @param <number> $value: the value to be converted to php ini format
     * @param <char> $unit: the current unit for the value
     * @return <ini entry> the smallest value and the largest possible unit
     */
    function convertToIniValue($value,$unit) {
        $newValue = $value;
        while(1) {
            $newValue = $value / 1024;
            if($newValue > 1) {
                $value = round($newValue,0);
                $this->increaseByteUnit($unit);
            } else
                break;
        }
        return("{$value}{$unit}");
    }

    /**
     * This function determines the next bigger unit of the
     * currently supplied unit as an inout parameter.
     * @param <type> $unit: the next bigger of the supplied unit
     */
    function increaseByteUnit(&$unit) {
        switch($unit) {
            case 'B' : $unit='K'; break;
            case 'K' : $unit='M'; break;
            case 'M' : $unit='G'; break;
            case 'G' : $unit='T'; break;
            default : $unit='X';
        }
    }
}
?>
